<?php
/**
 * 小程序预约详情API
 * 提供预约记录查询和详细信息获取功能
 * 支持获取用户关联的个人预约详情
 */

header('Content-Type: application/json; charset=utf-8');
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS');
header('Access-Control-Allow-Headers: Content-Type, Authorization');

if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') {
    exit;
}

// 数据库配置
$dbConfig = [
    'host' => 'localhost',
    'name' => 'nzy_congqian_cn', 
    'user' => 'nzy_congqian_cn',
    'pass' => 'FsnXrDfDhm4wFJSX',
    'charset' => 'utf8mb4'
];

// 微信小程序配置
$wxConfig = [
    'appid' => 'wxf7a6dfca45112e43',
    'secret' => '36895ffe99019fd5498f4e3bf400f0a0'
];

// 数据库连接
try {
    $dsn = "mysql:host={$dbConfig['host']};dbname={$dbConfig['name']};charset={$dbConfig['charset']}";
    $pdo = new PDO($dsn, $dbConfig['user'], $dbConfig['pass']);
    $pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch (PDOException $e) {
    jsonResponse([
        'success' => false,
        'message' => '数据库连接失败: ' . $e->getMessage()
    ]);
}

// 响应函数
function jsonResponse($data) {
    echo json_encode($data, JSON_UNESCAPED_UNICODE);
    exit;
}

function success($data = null, $message = '操作成功') {
    jsonResponse([
        'code' => 200,
        'success' => true,
        'message' => $message,
        'data' => $data,
        'timestamp' => time()
    ]);
}

function error($message = '操作失败', $code = 400) {
    jsonResponse([
        'code' => $code,
        'success' => false,
        'message' => $message,
        'data' => null,
        'timestamp' => time()
    ]);
}

// 验证微信用户token
function verifyWxToken($token) {
    global $pdo;
    
    if (empty($token)) {
        return null;
    }
    
    try {
        // 从token中获取用户信息
        $sql = "SELECT * FROM users WHERE openid = ? OR id = ?";
        $stmt = $pdo->prepare($sql);
        
        // 尝试将token作为openid或user_id查询
        $stmt->execute([$token, is_numeric($token) ? $token : 0]);
        $user = $stmt->fetch(PDO::FETCH_ASSOC);
        
        return $user;
    } catch (Exception $e) {
        return null;
    }
}

// 获取用户token
function getUserToken() {
    $headers = getallheaders();
    $authHeader = $headers['Authorization'] ?? $headers['authorization'] ?? '';
    
    if (strpos($authHeader, 'Bearer ') === 0) {
        return substr($authHeader, 7);
    }
    
    return $_GET['token'] ?? $_POST['token'] ?? $_GET['openid'] ?? $_POST['openid'] ?? '';
}

// 验证用户身份
$token = getUserToken();
$user = verifyWxToken($token);

if (!$user) {
    error('用户身份验证失败，请重新登录', 401);
}

// 获取用户的预约列表
function getUserReservationList() {
    global $pdo, $user;
    
    try {
        $page = max(1, (int)($_GET['page'] ?? 1));
        $limit = min(50, max(5, (int)($_GET['limit'] ?? 10)));
        $offset = ($page - 1) * $limit;
        
        // 构建查询条件
        $where = "r.user_id = ?";
        $params = [$user['id']];
        
        // 状态筛选
        if (isset($_GET['status']) && !empty($_GET['status'])) {
            $where .= " AND r.status = ?";
            $params[] = $_GET['status'];
        }
        
        // 预约类型筛选
        if (isset($_GET['type']) && !empty($_GET['type'])) {
            $where .= " AND r.reservation_type = ?";
            $params[] = $_GET['type'];
        }
        
        // 日期筛选
        if (isset($_GET['visit_date']) && !empty($_GET['visit_date'])) {
            $where .= " AND r.visit_date = ?";
            $params[] = $_GET['visit_date'];
        }
        
        // 查询总数
        $countSql = "SELECT COUNT(*) FROM reservations r WHERE $where";
        $countStmt = $pdo->prepare($countSql);
        $countStmt->execute($params);
        $total = $countStmt->fetchColumn();
        
        // 查询列表数据
        $sql = "SELECT 
                    r.id,
                    r.user_id,
                    r.personal_reservation_id,
                    r.reservation_type,
                    r.visit_date,
                    r.time_slot_id,
                    r.visitor_count,
                    r.visitor_name,
                    r.visitor_phone,
                    r.visitor_id_type,
                    r.visitor_id_card,
                    r.reservation_code,
                    r.qr_code_path,
                    r.status,
                    r.check_in_time,
                    r.notes,
                    r.created_at,
                    r.updated_at,
                    
                    -- 个人预约详细信息
                    pr.contact_name as personal_contact_name,
                    pr.contact_phone as personal_contact_phone,
                    pr.special_requirements,
                    pr.status as personal_status,
                    pr.review_note as personal_review_note,
                    
                    -- 时段信息
                    ts.name as time_slot_name,
                    ts.start_time,
                    ts.end_time,
                    ts.max_visitors,
                    
                    -- 团队预约信息（如果是团队预约）
                    tr.team_name,
                    tr.visitor_identity,
                    tr.contact_unit,
                    tr.need_guide,
                    tr.visitor_info as team_visitor_info
                    
                FROM reservations r
                LEFT JOIN personal_reservations pr ON r.personal_reservation_id = pr.id
                LEFT JOIN time_slots ts ON r.time_slot_id = ts.id
                LEFT JOIN team_reservations tr ON r.user_id = tr.user_id AND r.reservation_type = 'team'
                WHERE $where
                ORDER BY r.created_at DESC
                LIMIT ? OFFSET ?";
        
        $params[] = $limit;
        $params[] = $offset;
        
        $stmt = $pdo->prepare($sql);
        $stmt->execute($params);
        $reservations = $stmt->fetchAll(PDO::FETCH_ASSOC);
        
        // 格式化数据
        foreach ($reservations as &$reservation) {
            // 格式化状态
            $statusMap = [
                'pending' => '待确认',
                'confirmed' => '已确认',
                'cancelled' => '已取消',
                'completed' => '已完成',
                'expired' => '已过期'
            ];
            $reservation['status_text'] = $statusMap[$reservation['status']] ?? '未知';
            
            // 格式化预约类型
            $typeMap = [
                'personal' => '个人预约',
                'team' => '团队预约'
            ];
            $reservation['reservation_type_text'] = $typeMap[$reservation['reservation_type']] ?? '未知';
            
            // 时段信息格式化
            if ($reservation['start_time'] && $reservation['end_time']) {
                $reservation['time_slot_display'] = ($reservation['time_slot_name'] ?: '时段') . 
                    ' ' . substr($reservation['start_time'], 0, 5) . '-' . substr($reservation['end_time'], 0, 5);
            } else {
                $reservation['time_slot_display'] = '无指定时段';
            }
            
            // 联系人信息整合
            $reservation['contact_name'] = $reservation['personal_contact_name'] ?: 
                                         $reservation['visitor_name'] ?: 
                                         ($reservation['team_name'] ? '团队：' . $reservation['team_name'] : '未知');
            
            $reservation['contact_phone'] = $reservation['personal_contact_phone'] ?: $reservation['visitor_phone'];
            
            // 是否可以取消（只有未确认和已确认的可以取消，且距离参观时间24小时以上）
            $canCancel = in_array($reservation['status'], ['pending', 'confirmed']) && 
                        strtotime($reservation['visit_date'] . ' ' . ($reservation['start_time'] ?: '09:00:00')) > (time() + 24 * 3600);
            $reservation['can_cancel'] = $canCancel;
            
            // 是否可以修改（只有待确认的可以修改，且距离参观时间48小时以上）
            $canModify = $reservation['status'] == 'pending' && 
                        strtotime($reservation['visit_date'] . ' ' . ($reservation['start_time'] ?: '09:00:00')) > (time() + 48 * 3600);
            $reservation['can_modify'] = $canModify;
            
            // 是否显示二维码（已确认的预约）
            $reservation['show_qr_code'] = $reservation['status'] == 'confirmed' && !empty($reservation['qr_code_path']);
            
            // 去除敏感信息（身份证部分隐藏）
            if ($reservation['visitor_id_card'] && strlen($reservation['visitor_id_card']) > 6) {
                $reservation['visitor_id_card_display'] = substr($reservation['visitor_id_card'], 0, 3) . 
                    str_repeat('*', strlen($reservation['visitor_id_card']) - 6) . 
                    substr($reservation['visitor_id_card'], -3);
            } else {
                $reservation['visitor_id_card_display'] = $reservation['visitor_id_card'];
            }
        }
        
        success([
            'list' => $reservations,
            'pagination' => [
                'page' => $page,
                'limit' => $limit,
                'total' => (int)$total,
                'pages' => ceil($total / $limit)
            ]
        ]);
        
    } catch (Exception $e) {
        error('获取预约列表失败: ' . $e->getMessage(), 500);
    }
}

// 获取预约详情
function getReservationDetail() {
    global $pdo, $user;
    
    $id = $_GET['id'] ?? 0;
    if (!$id) {
        error('缺少预约ID');
    }
    
    try {
        $sql = "SELECT 
                    r.*,
                    
                    -- 个人预约详细信息
                    pr.contact_name as personal_contact_name,
                    pr.contact_phone as personal_contact_phone,
                    pr.special_requirements,
                    pr.status as personal_status,
                    pr.review_note as personal_review_note,
                    pr.created_at as personal_created_at,
                    
                    -- 时段信息
                    ts.name as time_slot_name,
                    ts.start_time,
                    ts.end_time,
                    ts.max_visitors,
                    ts.description as time_slot_description,
                    
                    -- 团队预约信息
                    tr.team_name,
                    tr.visitor_identity,
                    tr.contact_unit,
                    tr.need_guide,
                    tr.visitor_info as team_visitor_info,
                    tr.reservation_time as team_reservation_time,
                    tr.end_time as team_end_time
                    
                FROM reservations r
                LEFT JOIN personal_reservations pr ON r.personal_reservation_id = pr.id
                LEFT JOIN time_slots ts ON r.time_slot_id = ts.id
                LEFT JOIN team_reservations tr ON r.user_id = tr.user_id AND r.reservation_type = 'team'
                WHERE r.id = ? AND r.user_id = ?";
        
        $stmt = $pdo->prepare($sql);
        $stmt->execute([$id, $user['id']]);
        $reservation = $stmt->fetch(PDO::FETCH_ASSOC);
        
        if (!$reservation) {
            error('预约记录不存在或无权限访问');
        }
        
        // 格式化基本信息
        $statusMap = [
            'pending' => '待确认',
            'confirmed' => '已确认',
            'cancelled' => '已取消',
            'completed' => '已完成',
            'expired' => '已过期'
        ];
        $reservation['status_text'] = $statusMap[$reservation['status']] ?? '未知';
        
        $typeMap = [
            'personal' => '个人预约',
            'team' => '团队预约'
        ];
        $reservation['reservation_type_text'] = $typeMap[$reservation['reservation_type']] ?? '未知';
        
        // 时段信息
        if ($reservation['start_time'] && $reservation['end_time']) {
            $reservation['time_slot_display'] = ($reservation['time_slot_name'] ?: '时段') . 
                ' ' . substr($reservation['start_time'], 0, 5) . '-' . substr($reservation['end_time'], 0, 5);
        } else {
            $reservation['time_slot_display'] = '无指定时段';
        }
        
        // 联系人信息
        $reservation['contact_name'] = $reservation['personal_contact_name'] ?: $reservation['visitor_name'];
        $reservation['contact_phone'] = $reservation['personal_contact_phone'] ?: $reservation['visitor_phone'];
        
        // 操作权限
        $canCancel = in_array($reservation['status'], ['pending', 'confirmed']) && 
                    strtotime($reservation['visit_date'] . ' ' . ($reservation['start_time'] ?: '09:00:00')) > (time() + 24 * 3600);
        $reservation['can_cancel'] = $canCancel;
        
        $canModify = $reservation['status'] == 'pending' && 
                    strtotime($reservation['visit_date'] . ' ' . ($reservation['start_time'] ?: '09:00:00')) > (time() + 48 * 3600);
        $reservation['can_modify'] = $canModify;
        
        $reservation['show_qr_code'] = $reservation['status'] == 'confirmed' && !empty($reservation['qr_code_path']);
        
        // 获取同行人员信息（如果是个人预约）
        if ($reservation['reservation_type'] == 'personal') {
            $companionsSql = "SELECT name, id_type, id_number, phone 
                             FROM common_visitors 
                             WHERE user_id = ? 
                             ORDER BY updated_at DESC 
                             LIMIT 10";
            $companionsStmt = $pdo->prepare($companionsSql);
            $companionsStmt->execute([$user['id']]);
            $companions = $companionsStmt->fetchAll(PDO::FETCH_ASSOC);
            
            // 同行人员身份证脱敏
            foreach ($companions as &$companion) {
                if ($companion['id_number'] && strlen($companion['id_number']) > 6) {
                    $companion['id_number_display'] = substr($companion['id_number'], 0, 3) . 
                        str_repeat('*', strlen($companion['id_number']) - 6) . 
                        substr($companion['id_number'], -3);
                } else {
                    $companion['id_number_display'] = $companion['id_number'];
                }
            }
            
            $reservation['companions'] = $companions;
        }
        
        // 预约说明和注意事项
        $reservation['notice'] = [
            'cancellation_policy' => '距离参观时间24小时以内无法取消预约',
            'modification_policy' => '距离参观时间48小时以内无法修改预约',
            'check_in_policy' => '请在预约时间前15分钟到达进行签到',
            'qr_code_policy' => '请保存好二维码，入馆时需要出示',
            'contact_info' => '如有疑问请联系客服电话：400-123-4567'
        ];
        
        // 身份证脱敏
        if ($reservation['visitor_id_card'] && strlen($reservation['visitor_id_card']) > 6) {
            $reservation['visitor_id_card_display'] = substr($reservation['visitor_id_card'], 0, 3) . 
                str_repeat('*', strlen($reservation['visitor_id_card']) - 6) . 
                substr($reservation['visitor_id_card'], -3);
        } else {
            $reservation['visitor_id_card_display'] = $reservation['visitor_id_card'];
        }
        
        success($reservation);
        
    } catch (Exception $e) {
        error('获取预约详情失败: ' . $e->getMessage(), 500);
    }
}

// 根据预约码查询预约信息（用于分享等场景）
function getReservationByCode() {
    global $pdo, $user;
    
    $code = $_GET['code'] ?? '';
    if (!$code) {
        error('缺少预约码');
    }
    
    try {
        $sql = "SELECT 
                    r.id,
                    r.reservation_code,
                    r.reservation_type,
                    r.visit_date,
                    r.visitor_count,
                    r.visitor_name,
                    r.status,
                    r.qr_code_path,
                    ts.name as time_slot_name,
                    ts.start_time,
                    ts.end_time
                FROM reservations r
                LEFT JOIN time_slots ts ON r.time_slot_id = ts.id
                WHERE r.reservation_code = ? AND r.user_id = ?";
        
        $stmt = $pdo->prepare($sql);
        $stmt->execute([$code, $user['id']]);
        $reservation = $stmt->fetch(PDO::FETCH_ASSOC);
        
        if (!$reservation) {
            error('预约码不存在或无权限访问');
        }
        
        // 简化的状态信息
        $statusMap = [
            'pending' => '待确认',
            'confirmed' => '已确认',
            'cancelled' => '已取消',
            'completed' => '已完成',
            'expired' => '已过期'
        ];
        $reservation['status_text'] = $statusMap[$reservation['status']] ?? '未知';
        
        if ($reservation['start_time'] && $reservation['end_time']) {
            $reservation['time_slot_display'] = ($reservation['time_slot_name'] ?: '时段') . 
                ' ' . substr($reservation['start_time'], 0, 5) . '-' . substr($reservation['end_time'], 0, 5);
        }
        
        $reservation['show_qr_code'] = $reservation['status'] == 'confirmed' && !empty($reservation['qr_code_path']);
        
        success($reservation);
        
    } catch (Exception $e) {
        error('查询预约信息失败: ' . $e->getMessage(), 500);
    }
}

// 取消预约
function cancelReservation() {
    global $pdo, $user;
    
    $input = json_decode(file_get_contents('php://input'), true);
    $id = $input['id'] ?? 0;
    $reason = trim($input['reason'] ?? '');
    
    if (!$id) {
        error('缺少预约ID');
    }
    
    try {
        $pdo->beginTransaction();
        
        // 检查预约是否存在且属于当前用户
        $checkSql = "SELECT * FROM reservations WHERE id = ? AND user_id = ?";
        $checkStmt = $pdo->prepare($checkSql);
        $checkStmt->execute([$id, $user['id']]);
        $reservation = $checkStmt->fetch(PDO::FETCH_ASSOC);
        
        if (!$reservation) {
            throw new Exception('预约记录不存在或无权限操作');
        }
        
        // 检查是否可以取消
        if (!in_array($reservation['status'], ['pending', 'confirmed'])) {
            throw new Exception('当前状态无法取消预约');
        }
        
        // 检查时间限制（24小时内不能取消）
        $visitDateTime = strtotime($reservation['visit_date'] . ' 09:00:00'); // 默认9点开始
        if ($visitDateTime <= (time() + 24 * 3600)) {
            throw new Exception('距离参观时间不足24小时，无法取消预约');
        }
        
        // 更新预约状态
        $updateSql = "UPDATE reservations SET 
                        status = 'cancelled',
                        notes = CONCAT(COALESCE(notes, ''), '\n用户取消：', ?),
                        updated_at = NOW()
                      WHERE id = ?";
        $updateStmt = $pdo->prepare($updateSql);
        $updateStmt->execute([$reason ?: '用户主动取消', $id]);
        
        // 如果有关联的个人预约，也需要更新状态
        if ($reservation['personal_reservation_id']) {
            $updatePersonalSql = "UPDATE personal_reservations SET 
                                    status = 3,
                                    review_note = CONCAT(COALESCE(review_note, ''), '\n用户取消预约')
                                  WHERE id = ?";
            $updatePersonalStmt = $pdo->prepare($updatePersonalSql);
            $updatePersonalStmt->execute([$reservation['personal_reservation_id']]);
        }
        
        $pdo->commit();
        success(null, '预约已成功取消');
        
    } catch (Exception $e) {
        $pdo->rollBack();
        error('取消预约失败: ' . $e->getMessage(), 500);
    }
}

// 获取用户预约统计
function getUserReservationStats() {
    global $pdo, $user;
    
    try {
        // 用户预约统计
        $statsSql = "SELECT 
                        COUNT(*) as total,
                        COUNT(CASE WHEN status = 'pending' THEN 1 END) as pending_count,
                        COUNT(CASE WHEN status = 'confirmed' THEN 1 END) as confirmed_count,
                        COUNT(CASE WHEN status = 'completed' THEN 1 END) as completed_count,
                        COUNT(CASE WHEN status = 'cancelled' THEN 1 END) as cancelled_count,
                        COUNT(CASE WHEN reservation_type = 'personal' THEN 1 END) as personal_count,
                        COUNT(CASE WHEN reservation_type = 'team' THEN 1 END) as team_count
                     FROM reservations 
                     WHERE user_id = ?";
        $statsStmt = $pdo->prepare($statsSql);
        $statsStmt->execute([$user['id']]);
        $stats = $statsStmt->fetch(PDO::FETCH_ASSOC);
        
        // 即将到来的预约
        $upcomingSql = "SELECT 
                            r.id,
                            r.reservation_code,
                            r.visit_date,
                            r.visitor_count,
                            r.status,
                            ts.name as time_slot_name,
                            ts.start_time
                        FROM reservations r
                        LEFT JOIN time_slots ts ON r.time_slot_id = ts.id
                        WHERE r.user_id = ? 
                        AND r.visit_date >= CURDATE()
                        AND r.status IN ('pending', 'confirmed')
                        ORDER BY r.visit_date ASC, ts.start_time ASC
                        LIMIT 3";
        $upcomingStmt = $pdo->prepare($upcomingSql);
        $upcomingStmt->execute([$user['id']]);
        $upcoming = $upcomingStmt->fetchAll(PDO::FETCH_ASSOC);
        
        success([
            'stats' => $stats,
            'upcoming_reservations' => $upcoming
        ]);
        
    } catch (Exception $e) {
        error('获取统计信息失败: ' . $e->getMessage(), 500);
    }
}

// 处理请求
$method = $_SERVER['REQUEST_METHOD'];
$action = $_GET['action'] ?? '';

try {
    switch ($method) {
        case 'GET':
            switch ($action) {
                case 'list':
                    getUserReservationList();
                    break;
                case 'detail':
                    getReservationDetail();
                    break;
                case 'by_code':
                    getReservationByCode();
                    break;
                case 'stats':
                    getUserReservationStats();
                    break;
                default:
                    error('无效的操作');
            }
            break;
            
        case 'POST':
            switch ($action) {
                case 'cancel':
                    cancelReservation();
                    break;
                default:
                    error('无效的操作');
            }
            break;
            
        default:
            error('不支持的请求方法');
    }
    
} catch (PDOException $e) {
    error('数据库错误: ' . $e->getMessage(), 500);
} catch (Exception $e) {
    error('服务器错误: ' . $e->getMessage(), 500);
}
?>